<?php
/**
 * SLS_BoEdit Tool - Generate back-office editing
 *  
 * @author Laurent Bientz 
 * @copyright SillySmart
 * @package SLS.Generics.Tools.SLS_Bo
 * @since 1.0 
 */
class SLS_BoEdit
{		
	private $oController;
	private $model;
	private $db;
	private $_generic;
	private $http;
	private $xml;
	private $urlToRedirect;
	private $refSmod;
	public $error = false;
				
	/**
	 * Constructor
	 *
	 * @access public
	 * @param Object $oController reference of the current running controller
	 * @param string $model the model you want to allow adding
	 * @param SLS_XMLToolBox $xml the reference of the xmltoolbox
	 * @param string $alias the alias of the db
	 * @since 1.0
	 */
	public function __construct($oController,$model,$alias,$xml)
	{
		$this->oController = $oController;
		$this->model = $model;
		$this->db = $alias;
		$this->xml = $xml;
		$this->_generic = SLS_Generic::getInstance();
		$this->http = $this->_generic->getObjectHttpRequest();
		$this->xmlType = new SLS_XMLToolbox(file_get_contents($this->_generic->getPathConfig("configSls")."/types.xml"));		
		$this->xmlFk = new SLS_XMLToolbox(file_get_contents($this->_generic->getPathConfig("configSls")."/fks.xml"));
		$this->xmlFilter = new SLS_XMLToolbox(file_get_contents($this->_generic->getPathConfig("configSls")."/filters.xml"));
		$this->xmlBo = new SLS_XMLToolbox(file_get_contents($this->_generic->getPathConfig("configSls")."/backoffice.xml"));
		$this->xmlBearer = new SLS_XMLToolbox(file_get_contents($this->_generic->getPathConfig("configSls")."/bearers.xml"));
	}
	
	/**
	 * Set the url on which you want to go after the editing success
	 *
	 * @access public
	 * @param string $mod the generic mod (domainName if empty)
	 * @param string $smod the generic smod (domainName if empty)
	 * @since 1.0
	 */
	public function setUrlToRedirect($mod,$smod)
	{
		if ($mod != -1 && $smod != -1)
		{
			$session = $this->_generic->getObjectSession();
			$arrayPost = array();
			$this->refSmod = $smod;
			$post = $session->getParam("SLS_PREVIOUS_POST_".$smod);
			
			// If we have previous post
			if (!empty($mod) && !empty($smod) && !empty($post))
			{
		        $postExploded = explode("/",$post);
		        $postExploded = array_chunk($postExploded,2);	        
		        for($i=0 ; $i<$count=count($postExploded) ; $i++)        
		        	if (is_array($postExploded[$i]) && count($postExploded[$i]) == 2)        	
		        		array_push($arrayPost,array("key" => $postExploded[$i][0],"value" => $postExploded[$i][1]));
			}
			
			// If not url to redirect
			if (empty($mod) || empty($smod))
				$this->urlToRedirect = $this->_generic->getProtocol()."://".$this->_generic->getSiteConfig("domainName");
			else
				$this->urlToRedirect = $this->_generic->getFullPath($mod,$smod,$arrayPost);
		}
		else
			$this->urlToRedirect = "";
	}
	
	/**
	 * Construct the edit
	 *
	 * @access public
	 * @since 1.0
	 */
	public function constructEdit()
	{
		$class = ucfirst($this->db)."_".SLS_String::tableToClass($this->model);
		$this->_generic->useModel(SLS_String::tableToClass($this->model),$this->db);
		$object = new $class();		
		$firstLangError = "";
		$errors = array();
		$columns = array();
		
		$this->xml->startTag("bo_edit");
		
		// Recover id
		$id = $this->http->getParam("id");
		
		// If reload
		if ($this->http->getParam("reload_edit") == "true")
		{
			$bearersToRecord = array();
			$redirect_target = $this->http->getParam("redirect_target");
			$this->_generic->getObjectSession()->setParam("SLS_BO_REDIRECT_EDIT",$redirect_target);
			
			// Multilanguage case
			if ($object->isMultilanguage())
			{
				$langs 			= $this->_generic->getObjectLang()->getSiteLangs();
				$defaultLang 	= $this->_generic->getSiteConfig("defaultLang");
				$pk 			= $object->giveNextId();
				$params 		= $this->http->getParams();
				$clones			= array();
				
				// Foreach langs, catch errors
				foreach($langs as $lang)
				{					
					$object_{$lang} = new $class();
					$object_{$lang}->setModelLanguage($lang);
					$object_{$lang}->getModel($id);
					
					foreach($params as $key => $value)
					{
						// Bearers						
						if (SLS_String::startsWith($key,"bearer_") && $lang == $defaultLang)					
							$bearersToRecord[SLS_String::substrAfterFirstDelimiter($key,"bearer_")] = $value;
						else
						{
							if (SLS_String::endsWith($key,"_".$lang))
							{
								// MySQL Type Set
								if (is_array($value) && 
									!array_key_exists("name",$value) && 
									!array_key_exists("type",$value) &&
									!array_key_exists("tmp_name",$value) &&
									!array_key_exists("error",$value) && 
									!array_key_exists("size",$value))
								{
									$value = implode(",",$value);
								}
								
								$functionName 	= "set".SLS_String::fullTrim(ucwords(SLS_String::stringToUrl(str_replace("_"," ",SLS_String::substrBeforeLastDelimiter($key,"_"))," ",false)),"");						
								$columns[$key] 	= SLS_String::trimSlashesFromString($value);														
								$result = array_shift($this->xmlType->getTagsAttribute("//sls_configs/entry[@table='".$object_{$lang}->getDatabase()."_".$object_{$lang}->getTable()."' and @column='".SLS_String::substrBeforeLastDelimiter($key,"_")."' and (@type = 'file_all' or @type = 'file_img')]","multilanguage"));
								$noSet = (!empty($result) && (empty($columns[$key]) || (is_array($params[$key]) && $columns[$key]["error"] == "4"))) ? true : false;
																
								if (!$noSet && !$object_{$lang}->$functionName($columns[$key]))
									$this->error = true;
									
								// If current lang is the default lang
								if ($lang == $defaultLang)
								{
									// If we found a no-multilanguage column
									$result = array_shift($this->xmlBo->getTagsAttribute("//sls_configs/entry[@table='".$object_{$lang}->getDatabase()."_".$object_{$lang}->getTable()."' and @column='".SLS_String::substrBeforeLastDelimiter($key,"_")."' and @multilanguage = 'false']","multilanguage"));
									if (!empty($result) && !$this->error)
									{
										$clones[SLS_String::substrBeforeLastDelimiter($key,"_")] = $object_{$lang}->__get(SLS_String::substrBeforeLastDelimiter($key,"_"));									
									}
								}
							}
						}
					}
					
					if ($this->error && $firstLangError == "")
						$firstLangError = $lang;
				}
				// If no errors, it's very cool, good admin =)
				if (!$this->error)
				{
					// Fill clones
					foreach ($langs as $lang)
					{
						if ($lang != $defaultLang)
						{
							foreach($clones as $key => $value)
							{
								$functionName 	= "set".SLS_String::fullTrim(ucwords(SLS_String::stringToUrl(str_replace("_"," ",$key)," ",false)),"");
								$object_{$lang}->$functionName($value);								
							}
						}
					}
					
					// Save objects
					foreach ($langs as $lang)
					{
						$object_{$lang}->save();
					}
					
					// Create bearers
					foreach($bearersToRecord as $bearersToRecordClass => $bearerToRecordValues)
					{
						// Objects
						$result = array_shift($this->xmlBearer->getTagsAttributes("//sls_configs/entry[@tableBearer='".$bearersToRecordClass."']",array("table1","table2")));						
						$this->_generic->useModel(SLS_String::substrAfterFirstDelimiter($bearersToRecordClass,"_"));
						$this->_generic->useModel(SLS_String::substrAfterFirstDelimiter($result["attributes"][0]["value"],"_"));
						$this->_generic->useModel(SLS_String::substrAfterFirstDelimiter($result["attributes"][1]["value"],"_"));						
						$objectBearer = new $bearersToRecordClass();
						$objectBearerTarget1 = new $result["attributes"][0]["value"]();
						$objectBearerTarget2 = new $result["attributes"][1]["value"]();
						$setterBearerTarget1 = "set".SLS_String::fullTrim(ucwords(SLS_String::stringToUrl(str_replace("_"," ",$objectBearerTarget1->getPrimaryKey())," ",false)),"");
						$setterBearerTarget2 = "set".SLS_String::fullTrim(ucwords(SLS_String::stringToUrl(str_replace("_"," ",$objectBearerTarget2->getPrimaryKey())," ",false)),"");
						
						// Clear old bearers
						$objectBearer->deleteModels($objectBearer->getTable(),array(),array(0=>array("column"=>$object->getPrimaryKey(),"value"=>$id,"mode"=>"equal")));
						
						// Save new bearers
						foreach($bearerToRecordValues as $bearerToRecordValue)
						{
							$objectBearer = new $bearersToRecordClass();
							$objectBearer->$setterBearerTarget1($id);
							$objectBearer->$setterBearerTarget2($bearerToRecordValue);
							$objectBearer->create();
							$objectBearer->save();
						}
					}
				}
				else
				{
					foreach($langs as $lang)
					{
						$errors[$lang] = $object_{$lang}->getErrors();
					}
				}
			}
			
			// Unilanguage case, less generic !
			else
			{
				$lang = $this->_generic->getSiteConfig("defaultLang");
				$objectNl = new $class();
				$objectNl->getModel($id);
				$params = $this->http->getParams();
				
				// Catch errors
				foreach($params as $key => $value)
				{
					// Bearers
					if (SLS_String::startsWith($key,"bearer_"))					
						$bearersToRecord[SLS_String::substrAfterFirstDelimiter($key,"bearer_")] = $value;
					else
					{
						// MySQL Type Set
						if (is_array($value) && 
							!array_key_exists("name",$value) && 
							!array_key_exists("type",$value) &&
							!array_key_exists("tmp_name",$value) &&
							!array_key_exists("error",$value) && 
							!array_key_exists("size",$value))
						{
							$value = implode(",",$value);
						}
								
						if (SLS_String::endsWith($key,"_".$lang))
						{							
							$noSet = (is_array($params[$key]) && $params[$key]["error"] == "4") ? true : false;
							
							$functionName = "set".SLS_String::fullTrim(ucwords(SLS_String::stringToUrl(str_replace("_"," ",SLS_String::substrBeforeLastDelimiter($key,"_"))," ",false)),"");						
							$columns[$key] = SLS_String::trimSlashesFromString($value);
													
							if (!$noSet && !$objectNl->$functionName($columns[$key]))
								$this->error = true;
						}
					}
				}
				
				// If no errors
				if (!$this->error)
				{
					// Save objects
					$objectNl->save();
					
					// Create bearers
					foreach($bearersToRecord as $bearersToRecordClass => $bearerToRecordValues)
					{
						// Objects
						$result = array_shift($this->xmlBearer->getTagsAttributes("//sls_configs/entry[@tableBearer='".$bearersToRecordClass."']",array("table1","table2")));						
						$this->_generic->useModel(SLS_String::substrAfterFirstDelimiter($bearersToRecordClass,"_"));
						$this->_generic->useModel(SLS_String::substrAfterFirstDelimiter($result["attributes"][0]["value"],"_"));
						$this->_generic->useModel(SLS_String::substrAfterFirstDelimiter($result["attributes"][1]["value"],"_"));						
						$objectBearer = new $bearersToRecordClass();
						$objectBearerTarget1 = new $result["attributes"][0]["value"]();
						$objectBearerTarget2 = new $result["attributes"][1]["value"]();
						$setterBearerTarget1 = "set".SLS_String::fullTrim(ucwords(SLS_String::stringToUrl(str_replace("_"," ",$objectBearerTarget1->getPrimaryKey())," ",false)),"");
						$setterBearerTarget2 = "set".SLS_String::fullTrim(ucwords(SLS_String::stringToUrl(str_replace("_"," ",$objectBearerTarget2->getPrimaryKey())," ",false)),"");
						
						// Clear old bearers
						$objectBearer->deleteModels($objectBearer->getTable(),array(),array(0=>array("column"=>$object->getPrimaryKey(),"value"=>$id,"mode"=>"equal")));
						
						// Save new bearers
						foreach($bearerToRecordValues as $bearerToRecordValue)
						{
							$objectBearer = new $bearersToRecordClass();
							$objectBearer->$setterBearerTarget1($id);
							$objectBearer->$setterBearerTarget2($bearerToRecordValue);
							$objectBearer->create();
							$objectBearer->save();
						}
					}
				}				
				else
				{
					$firstLangError = $lang;
					$errors[$lang] = $objectNl->getErrors();
				}
			}
			
			// If any errors, redirect on the user request page
			if (!$this->error && !empty($this->urlToRedirect))
			{
				$session = $this->_generic->getObjectSession();
				$session->delParam("SLS_PREVIOUS_POST_".$this->refSmod);
				
				$this->urlToRedirect = $this->_generic->getProtocol()."://".$this->_generic->getSiteConfig("domainName")."/".array_shift($this->_generic->getControllersXML()->getTags("//controllers/controller[@isBo='true']/@name"))."/List".ucfirst(strtolower($this->db))."_".SLS_String::tableToClass($this->model).".sls";
				if ($redirect_target == "list")
					$this->urlToRedirect = $this->_generic->getProtocol()."://".$this->_generic->getSiteConfig("domainName")."/".array_shift($this->_generic->getControllersXML()->getTags("//controllers/controller[@isBo='true']/@name"))."/List".ucfirst(strtolower($this->db))."_".SLS_String::tableToClass($this->model).".sls";
				else if ($redirect_target == "edit")
					$this->urlToRedirect = $this->_generic->getProtocol()."://".$this->_generic->getSiteConfig("domainName")."/".array_shift($this->_generic->getControllersXML()->getTags("//controllers/controller[@isBo='true']/@name"))."/Modify".ucfirst(strtolower($this->db))."_".SLS_String::tableToClass($this->model)."/id/".$this->http->getParam("id")."/SuccessEdit/True.sls";
				
				header("Location: ".$this->urlToRedirect);				
			}
			// Else, form the xml of the user
			else
			{
				$this->xml->startTag("reload");
				$this->xml->addFullTag("id",$id,true);
				$this->xml->addFullTag("error",($this->error) ? "true" : "false",true);
				$this->xml->addFullTag("first_lang_error",$firstLangError,true);
				$this->xml->startTag("properties");
				foreach($columns as $column => $value)
				{
					$property 		= SLS_String::substrBeforeLastDelimiter($column,"_");
					$lang 			= SLS_String::substrAfterLastDelimiter($column,"_");					
					$currentError 	= (empty($errors[$lang][$property])) ? "" : $GLOBALS[$GLOBALS['PROJECT_NAME']]['JS']['SLS_'.$errors[$lang][$property]];					
					
					if (is_array($value) && (empty($value) || $value["error"]["error"] == "4"))
					{
						$object_{$lang} = new $class();
						$object_{$lang}->setModelLanguage($lang);
						if ($object_{$lang}->getModel($id) === true)
							$value = $object_{$lang}->__get($property);
					}
					
					$this->xml->startTag("property");
					$this->xml->addFullTag("name",$column,true);
					$this->xml->addFullTag("column",$property,true);
					$this->xml->addFullTag("lang",$lang,true);
					$this->xml->addFullTag("value",$value,true);
					$this->xml->addFullTag("label",$this->http->getParam($property."_".$lang."_label"),true);
					$this->xml->addFullTag("error",$currentError,true);					
					$this->xml->endTag("property");
				}
				$this->xml->endTag("properties");
				if (!empty($bearersToRecord))
				{
					$this->xml->startTag("bearers");
					foreach($bearersToRecord as $bearersToRecordClass => $bearerToRecordValues)
					{
						$result = array_shift($this->xmlBearer->getTagsAttributes("//sls_configs/entry[@tableBearer='".$bearersToRecordClass."']",array("table1","table2")));
						$bearerDb = ucfirst(SLS_String::substrBeforeFirstDelimiter($bearersToRecordClass,"_"));
						$bearerUse = SLS_String::substrAfterFirstDelimiter($bearersToRecordClass,"_");
						$bearerClass = $bearersToRecordClass;
						$bearerTargetDb = ucfirst(SLS_String::substrBeforeFirstDelimiter($result["attributes"][1]["value"],"_"));
						$bearerTargetUse = SLS_String::substrAfterFirstDelimiter($result["attributes"][1]["value"],"_");
						$bearerTargetClass = $result["attributes"][1]["value"];
						$this->_generic->useModel($bearerUse,$bearerDb);
						$this->_generic->useModel($bearerTargetUse,$bearerTargetDb);
						$bearerObject = new $bearerClass();
						$bearerTargetObject = new $bearerTargetClass();
						$resultFk = array_shift($this->xmlFk->getTagsAttribute("//sls_configs/entry[@tableFk='".strtolower($bearerClass)."' and @columnFk='".$bearerTargetObject->getPrimaryKey()."' and @tablePk = '".strtolower($bearerTargetDb)."_".$bearerTargetUse."']","labelPk"));
						$labelFk = (empty($resultFk)) ? $bearerTargetObject->getPrimaryKey() : $resultFk["attribute"];
						$str = $labelFk;
						$values = array();
						$masks = array();
						
						foreach($bearerTargetObject->getParams() as $key => $value)		
							array_push($masks,$key);
										
						$bearerTargetResults = $bearerTargetObject->searchModels("",array(),array(array("column"=>$bearerTargetObject->getPrimaryKey(),"value"=>$bearerToRecordValues,"mode"=>"in")));
						for($i=0 ; $i<$count=count($bearerTargetResults) ; $i++)
						{							
							$replacement = array();
							foreach($masks as $cur_mask)
								array_push($replacement,trim($bearerTargetResults[$i]->{$cur_mask}));
										
							$tmp = array("id"	=>$bearerTargetResults[$i]->{$bearerTargetObject->getPrimaryKey()},
										 "label"=>str_replace($masks,$replacement,$str));
							array_push($values,$tmp);
						}
						
						$this->xml->startTag("bearer");
							$this->xml->addFullTag("class",$bearersToRecordClass,true);
							$this->xml->startTag("properties");				
								foreach($values as $item => $curr_bearer)					
								{
									$this->xml->startTag("property");
										$this->xml->addFullTag("name",$curr_bearer["label"],true);
										$this->xml->addFullTag("id",$curr_bearer["id"],true);
									$this->xml->endTag("property");
								}										
							$this->xml->endTag("properties");
						$this->xml->endTag("bearer");
					}
					$this->xml->endTag("bearers");
				}
				$this->xml->endTag("reload");
			}
		}
		// Else, form the actual model
		else
		{
			$langs 	= $this->_generic->getObjectLang()->getSiteLangs();
			$columns = array();
			
			// If multilanguage
			if ($object->isMultilanguage())
			{
				foreach($langs as $lang)
				{
					$object_{$lang} = new $class();
					$object_{$lang}->setModelLanguage($lang);
					$object_{$lang}->getModel($id);
					$props = $object_{$lang}->getParams();
					
					foreach($props as $key => $value)					
						if ($key != $object_{$lang}->getPrimaryKey() && $key != "pk_lang")
							$columns[$key."_".$lang] = $value;
				}
			}
			// Else, just recover the model
			else
			{
				$lang = $this->_generic->getSiteConfig("defaultLang");
				$objectN1 = new $class();
				$objectN1->getModel($id);
				$props = $objectN1->getParams();
				foreach($props as $key => $value)				
					if ($key != $objectN1->getPrimaryKey() && $key != "pk_lang")
						$columns[$key."_".$lang] = $value;				
			}
			
			$this->xml->startTag("reload");
			
			// Table infos
			$this->xml->addFullTag("id",$id,true);
			$this->xml->addFullTag("error","false",true);
			// /Table infos
			
			// Table properties
			$this->xml->startTag("properties");				
			foreach($columns as $column => $value)
			{
				$property 		= SLS_String::substrBeforeLastDelimiter($column,"_");
				$lang 			= SLS_String::substrAfterLastDelimiter($column,"_");				
				$this->xml->startTag("property");
				$this->xml->addFullTag("name",$column,true);
				$this->xml->addFullTag("column",$property,true);
				$this->xml->addFullTag("lang",$lang,true);
				$this->xml->addFullTag("value",$value,true);
				$this->xml->addFullTag("error","",true);					
				$this->xml->endTag("property");
			}
			$this->xml->endTag("properties");
			// /Table properties
			
			// Table bearer
			$results = $this->xmlBearer->getTagsAttributes("//sls_configs/entry[@table1='".$class."']",array("tableBearer","table1","table2"));
			if (!empty($results))
			{
				$this->xml->startTag("bearers");
				for($i=0 ; $i<$count=count($results) ; $i++)
				{	
					$this->_generic->useModel(SLS_String::substrAfterFirstDelimiter($results[$i]["attributes"][0]["value"],"_"));
					$this->_generic->useModel(SLS_String::substrAfterFirstDelimiter($results[$i]["attributes"][1]["value"],"_"));
					$this->_generic->useModel(SLS_String::substrAfterFirstDelimiter($results[$i]["attributes"][2]["value"],"_"));						
					$objectBearer = new $results[$i]["attributes"][0]["value"]();
					$objectBearerTarget1 = new $results[$i]["attributes"][1]["value"]();
					$objectBearerTarget2 = new $results[$i]["attributes"][2]["value"]();
					$valuesChecked = ""; 

					$resultFk = array_shift($this->xmlFk->getTagsAttribute("//sls_configs/entry[@tableFk='".strtolower($results[$i]["attributes"][0]["value"])."' and @columnFk='".$objectBearerTarget2->getPrimaryKey()."' and @tablePk = '".strtolower(SLS_String::substrBeforeFirstDelimiter($results[$i]["attributes"][2]["value"], "_"))."_".SLS_String::substrAfterFirstDelimiter($results[$i]["attributes"][2]["value"], "_")."']","labelPk"));
					$labelFk = (empty($resultFk)) ? $objectBearerTarget2->getPrimaryKey() : $resultFk["attribute"];
					$str = $labelFk;
					$values = array();
					$masks = array();
					
					foreach($objectBearerTarget2->getParams() as $key => $value)		
						array_push($masks,$key);
					
					$checkeds = $objectBearer->searchModels($objectBearer->getTable(),array($objectBearerTarget2->getTable()),array(0=>array("column"=>$objectBearerTarget1->getPrimaryKey(),"value"=>$id,"mode"=>"equal")),array($objectBearerTarget2->getPrimaryKey()));					
					for($i=0 ; $i<$count=count($checkeds) ; $i++)
					{							
						$replacement = array();
						foreach($masks as $cur_mask)
							array_push($replacement,trim($checkeds[$i]->{$cur_mask}));
						
						$tmp = array("id"	=>$checkeds[$i]->{$objectBearerTarget2->getPrimaryKey()},
									 "label"=>str_replace($masks,$replacement,$str));
						array_push($values,$tmp);
					}
										
					$this->xml->startTag("bearer");
						$this->xml->addFullTag("class",ucfirst($objectBearer->getDatabase())."_".SLS_String::tableToClass($objectBearer->getTable()),true);						
						$this->xml->startTag("properties");
						foreach($values as $item => $curr_bearer)					
						{
							$this->xml->startTag("property");
								$this->xml->addFullTag("name",$curr_bearer["label"],true);
								$this->xml->addFullTag("id",$curr_bearer["id"],true);
							$this->xml->endTag("property");
						}
						$this->xml->endTag("properties");
					$this->xml->endTag("bearer");
				}
				$this->xml->endTag("bearers");
			}
			// /Table bearer			
			
			$this->xml->endTag("reload");
		}
		
		// If we are in "quick add mode"
		if ($this->http->getParam("SlsQuick") == "iFrame")		
			$this->_generic->setCurrentTpl("bo_light");
		
		// Get all properties, labels, values, types & length
		$properties = $this->getProperties();
		$description = $object->getTableComment($object->getTable(),$this->db);
		
		// Table infos
		$this->xml->addFullTag("table",$this->model,true);
		$this->xml->addFullTag("description",(empty($description)) ? ucfirst($object->getTable()) : $description,true);
		$this->xml->addFullTag("class",SLS_String::tableToClass($this->model),true);
		$this->xml->addFullTag("db",$object->getDatabase(),true);
		$this->xml->addFullTag("pk",$object->getPrimaryKey(),true);
		$this->xml->addFullTag("previous_success_add",($this->http->getParam("SuccessAdd") == "True") ? "true" : "false",true);
		$this->xml->addFullTag("previous_success_edit",($this->http->getParam("SuccessEdit") == "True") ? "true" : "false",true);
		$this->xml->addFullTag("current_url",$this->_generic->getFullPath(array_shift($this->_generic->getControllersXML()->getTags("//controllers/controller[@isBo='true']/@name")),"Modify".ucfirst(strtolower($this->db))."_".SLS_String::tableToClass($this->model),array(array("key"=>"id","value"=>$this->http->getParam("id")))),true);
		$this->xml->addFullTag("redirect_target",$this->_generic->getObjectSession()->getParam("SLS_BO_REDIRECT_EDIT"),true);
		$this->xml->addFullTag("email_url",(SLS_BoRights::isAuthorized("email",ucfirst(strtolower($this->db))."_".SLS_String::tableToClass($this->model))) ? $this->_generic->getFullPath(array_shift($this->_generic->getControllersXML()->getTags("//controllers/controller[@isBo='true']/@name")),"Email".ucfirst(strtolower($this->db))."_".SLS_String::tableToClass($this->model),array(),false) : "",true);		
		$this->xml->addFullTag("multilanguage",$object->isMultilanguage(),true);
		// /Table infos
		
		// Table langs
		$this->xml->startTag("langs");		
		if ($object->isMultilanguage())
		{
			$langs = $this->_generic->getObjectLang()->getSiteLangs();
			$this->xml->addFullTag("lang",$this->_generic->getObjectLang()->getDefaultLang(),true);	
			foreach($langs as $lang)
				if ($lang != $this->_generic->getObjectLang()->getDefaultLang())
					$this->xml->addFullTag("lang",$lang,true);
		}
		else
			$this->xml->addFullTag("lang",$this->_generic->getSiteConfig("defaultLang"),true);
		$this->xml->endTag("langs");
		// /Table langs
		
		// Table properties
		$this->xml->startTag("properties");
		for($i=0 ; $i<$count=count($properties) ; $i++)
		{
			$this->xml->startTag("property");
			foreach($properties[$i] as $key => $value)
				if ($key != "form_values" && $key != "form_thumbs" && $key != "js_filters")
					$this->xml->addFullTag($key,$value,true);
			
			$filters = $properties[$i]["js_filters"];			
			if (is_array($filters))
			{
				$this->xml->startTag("js_filters");
				for($j=0 ; $j<$countj=count($filters) ; $j++)								
					$this->xml->addFullTag("js_filter",$filters[$j],true);					
				$this->xml->endTag("js_filters");
			}
					
			$tmp = $properties[$i]["form_values"];
			$tmpThumbs = $properties[$i]["form_thumbs"];
			if (is_array($tmp) && !empty($tmp) && $properties[$i]["form_type"] != "radio")
			{
				$this->xml->startTag("values");
				for($j=0 ; $j<$countj=count($tmp) ; $j++)
				{
					$this->xml->startTag("value");
					$this->xml->addFullTag("id",$tmp[$j]["id"],true);
					$this->xml->addFullTag("label",$tmp[$j]["label"],true);
					$this->xml->addFullTag("lang",$tmp[$j]["lang"],true);
					$this->xml->endTag("value");
				}
				$this->xml->endTag("values");
			}
			else if (is_array($tmpThumbs) && !empty($tmpThumbs) && $properties[$i]["form_type"] != "radio")
			{
				$this->xml->startTag("thumbs");
				for($j=0 ; $j<$countj=count($tmpThumbs) ; $j++)
				{
					$this->xml->startTag("thumb");
					foreach($tmpThumbs[$j] as $key => $value)
						$this->xml->addFullTag($key,$value,true);
					$this->xml->endTag("thumb");
				}
				$this->xml->endTag("thumbs");
			}
			else if ($properties[$i]["form_type"] == "radio")
			{
				$this->xml->startTag("values");
				for($j=0 ; $j<$countj=count($tmp) ; $j++)
				{						
					$this->xml->addFullTag("value",$tmp[$j],true);
				}
				$this->xml->endTag("values");
			}
			else
			{
				$this->xml->addFullTag("values",(empty($tmp)) ? "-1" : $tmp,true);
				$this->xml->addFullTag("thumbs",(empty($tmpThumbs)) ? "-1" : $tmpThumbs,true);
			}
			$this->xml->endTag("property");
		}
		$this->xml->endTag("properties");
		// /Table properties
		
		// Table bearer
		$bearers = $this->xmlBearer->getTagsAttributes("//sls_configs/entry[@table1='".$class."']",array("tableBearer","table2"));		
		if (!empty($bearers))
		{
			$this->xml->startTag("bearers");
			for($j=0 ; $j<$countJ=count($bearers) ; $j++)
			{
				$bearerDb = ucfirst(SLS_String::substrBeforeFirstDelimiter($bearers[$j]["attributes"][0]["value"],"_"));
				$bearerUse = SLS_String::substrAfterFirstDelimiter($bearers[$j]["attributes"][0]["value"],"_");
				$bearerClass = $bearers[$j]["attributes"][0]["value"];
				$bearerTargetDb = ucfirst(SLS_String::substrBeforeFirstDelimiter($bearers[$j]["attributes"][1]["value"],"_"));
				$bearerTargetUse = SLS_String::substrAfterFirstDelimiter($bearers[$j]["attributes"][1]["value"],"_");
				$bearerTargetClass = $bearers[$j]["attributes"][1]["value"];
				$this->_generic->useModel($bearerUse,$bearerDb);
				$this->_generic->useModel($bearerTargetUse,$bearerTargetDb);
				$bearerObject = new $bearerClass();
				$bearerTargetObject = new $bearerTargetClass();
				$resultFk = array_shift($this->xmlFk->getTagsAttribute("//sls_configs/entry[@tableFk='".strtolower($bearerClass)."' and @columnFk='".$bearerTargetObject->getPrimaryKey()."' and @tablePk = '".strtolower($bearerTargetDb)."_".$bearerTargetUse."']","labelPk"));
				$labelFk = (empty($resultFk)) ? $bearerTargetObject->getPrimaryKey() : $resultFk["attribute"];
				$str = $labelFk;
				$values = array();
				$masks = array();
				
				foreach($bearerTargetObject->getParams() as $key => $value)		
					array_push($masks,$key);
				
				foreach($bearerTargetObject->getParams() as $key => $value)					
					if (SLS_String::contains($labelFk,$key))
						$labelFk = str_replace($key,$bearerTargetObject->getColumnComment($key),$labelFk);
						
				$urlAddFk = $this->_generic->getFullPath($controllerBo = array_shift($this->_generic->getControllersXML()->getTags("//controllers/controller[@isBo='true']/@name")),"Add".$bearerTargetClass,
																		  array(array("key" => "SlsQuick", "value" => "iFrame")),false);	
				
				$this->xml->startTag("bearer");
					$this->xml->addFullTag("table",$bearerObject->getTable(),true);
					$this->xml->addFullTag("class",$bearerClass,true);
					$this->xml->addFullTag("description",$bearerObject->getTableComment(),true);
					$this->xml->addFullTag("url_ac_pattern",$labelFk,true);
					$this->xml->addFullTag("url_add_fk",$urlAddFk,true);
					$this->xml->addFullTag("url_ac",$this->_generic->getFullPath($controllerBo = array_shift($this->_generic->getControllersXML()->getTags("//controllers/controller[@isBo='true']/@name")),"FkAC",
																				  array(array("key" => "Model",	"value" => SLS_String::substrAfterFirstDelimiter($bearerClass,"_")),
																						array("key" => "Db",	"value" => strtolower(SLS_String::substrBeforeFirstDelimiter($bearerClass,"_"))),
																						array("key" => "Column","value" => $bearerTargetObject->getPrimaryKey()),
																						array("key" => "Lang",	"value" => $this->_generic->getObjectLang()->getDefaultLang())),true),true);					
				$this->xml->endTag("bearer");
			}
			$this->xml->endTag("bearers");
		}
		// /Table bearer
		
		$this->xml->endTag("bo_edit");
		
		return $this->xml;
	}
	
	/**
	 * Get all the columns from the current table
	 *
	 * @access public
	 * @return array $properties all the columns informations
	 * @since 1.0
	 */
	public function getProperties()
	{
		$properties = array();
		$sql = SLS_Sql::getInstance();
		
		$this->_generic->useModel(SLS_String::tableToClass($this->model),$this->db);
		$class = ucfirst($this->db)."_".SLS_String::tableToClass($this->model);
		$currentModel = new $class();
		$columns = $sql->showColumns($currentModel->getTable());
		$defaultMultilanguage = ($currentModel->isMultilanguage()) ? "true" : "false";
		$nullable = false;
				
		for($i=0 ; $i<$count=count($columns) ; $i++)
		{
			$nullable = ($columns[$i]->Null == "NO") ? "false" : "true";
			$urlDelete = "";
			if ($columns[$i]->Key != "PRI")
			{
				$column = $columns[$i]->Field;
				$type = (strpos($columns[$i]->Type, "(")) ? SLS_String::substrBeforeFirstDelimiter(strtolower($columns[$i]->Type), "(") : $columns[$i]->Type;
								
				if (SLS_String::startsWith($type,"float") || SLS_String::startsWith($type,"double") || SLS_String::startsWith($type,"decimal"))
				{
					$length = SLS_String::substrBeforeFirstDelimiter(SLS_String::substrAfterFirstDelimiter(SLS_String::substrBeforeLastDelimiter($columns[$i]->Type, ')'), '('), ",");
					if (empty($length))
						$length = "25";
					$values = array();
					$form = "input_text";
					$align = "right";
					$multilanguage = $defaultMultilanguage;
					$fk = -1;
					$typeFile = -1;
					$thumbs = array();
					$date = "false";
					$color = "false";
					$urlAC = "";
					$jsType = "float";
					$jsSpecificType = "";
				}
				else if ($type == "enum")
				{
					$length = -1;
					$values = explode("','",SLS_String::substrAfterFirstDelimiter(SLS_String::substrBeforeLastDelimiter($columns[$i]->Type, "')"), "('"));
					if ($columns[$i]->Null == "YES")
						array_unshift($values,"sls_enum_empty");
					$form = "radio";
					$align = "left";
					$multilanguage = $defaultMultilanguage;
					$fk = -1;
					$date = "false";
					$color = "false";
					$defaultValue = $columns[$i]->Default;
					$urlAC = "";
					$jsType = "radio";
					$jsSpecificType = "";
				}
				else if ($type == "set")
				{
					$form = "select_multiple";
					$align = "right";
					$multilanguage = $defaultMultilanguage;
					$length = -1;
					$fk = -1;
					$date = "false";
					$color = "false";
					$defaultValue = $columns[$i]->Default;
					$urlAC = "";
					$jsType = "checkbox";
					$jsSpecificType = "";
					
					$values = array();
					$arrayTmp = explode("','",SLS_String::substrBeforeLastDelimiter(SLS_String::substrAfterFirstDelimiter($columns[$i]->Type,"set('"),"')"));					
					if ($columns[$i]->Null == "YES")
					{
						$tmp = array("id"	=>"",
									 "label"=>"",
									 "lang" =>"");
						array_push($values,$tmp);
					}
					foreach($arrayTmp as $array)
					{						
						$tmp = array("id"	=>$array,
									 "label"=>$array,
									 "lang" =>"");
						array_push($values,$tmp);
					}
				}
				else if (SLS_String::endsWith($type,"text"))
				{
					$length = -1;
					$values = array();
					$form = "textarea";
					$align = "left";
					$multilanguage = $defaultMultilanguage;
					$fk = -1;
					$typeFile = -1;
					$thumbs = array();
					$date = "false";
					$color = "false";
					$urlAC = "";
					$jsType = "string";
					$jsSpecificType = "";
				}
				else 
				{					
					if (strpos($columns[$i]->Type, "("))
					{
						$length = SLS_String::substrAfterFirstDelimiter(SLS_String::substrBeforeLastDelimiter($columns[$i]->Type, ")"), "(");
						$values = array();
						$form = "input_text";
						$align = "left";
						$multilanguage = $defaultMultilanguage;
						$fk = -1;
						$typeFile = -1;
						$thumbs = array();
						$date = "false";
						$color = "false";
						$urlAC = "";
						$jsType = "string";
						$jsSpecificType = "";
					}
					if(SLS_String::endsWith($type, "int"))
					{
						$length = SLS_String::substrAfterFirstDelimiter(SLS_String::substrBeforeLastDelimiter($columns[$i]->Type, ")"), "(");
						$values = array();
						$form = "input_text";
						$align = "left";
						$multilanguage = $defaultMultilanguage;
						$fk = -1;
						$typeFile = -1;
						$thumbs = array();
						$date = "false";
						$color = "false";
						$urlAC = "";
						$jsType = "int";
						$jsSpecificType = "";
					}
					else if ($type == "date" || $type == "datetime" || $type == "timestamp" || $type == "time" || $type == "year")
					{
						$length = -1;
						$form = "input_text";
						$align = "right";
						$multilanguage = $defaultMultilanguage;
						$fk = -1;
						$typeFile = -1;
						$thumbs = array();
						$date = $type;
						$color = "false";
						$urlAC = "";
						$jsType = "string";
						$jsSpecificType = $type;
						
						if ($columns[$i]->Null != "YES")
						{
							switch ($type)
							{
								case "date":		$values = date("Y-m-d"); 		break;
								case "datetime":	$values = date("Y-m-d H:i:s"); 	break;
								case "timestamp": 	$values = date("Y-m-d H:i:s"); 	break;
								case "time":		$values = date("H:i:s"); 		break;
								case "year":		$values = date("Y"); 			break;
							}
						}
					}
				}
				
				// Search specific type
				$result = array_shift($this->xmlType->getTags("//sls_configs/entry[@table='".$this->db."_".$currentModel->getTable()."' and @column='".$column."']/@type"));
				if (!empty($result))
					$jsSpecificType = $result;
				
				// Search type file
				$result = array_shift($this->xmlType->getTagsAttributes("//sls_configs/entry[@table='".$this->db."_".$currentModel->getTable()."' and @column='".$column."' and (@type='file_img' or @type='file_all')]",array("type","multilanguage","thumbs")));				
				if (!empty($result) && count($result["attributes"]) == 3)
				{
					$length = -1;
					$values = array();
					$form = "input_file";
					$align = "left";
					$multilanguage = $result["attributes"][1]["value"];
					$fk = -1;
					$typeFile = $result["attributes"][0]["value"];
					$thumbs = unserialize(str_replace("||#||",'"',$result["attributes"][2]["value"]));
					$date = "false";
					$color = "false";
					$urlAC = "";
					$jsType = $result["attributes"][0]["value"];
					$jsSpecificType = "file";
					$nullable = "true";
					if (($columns[$i]->Null == "YES"))
					{
						$urlDelete = $this->_generic->getFullPath($controllerBo = array_shift($this->_generic->getControllersXML()->getTags("//controllers/controller[@isBo='true']/@name")), "DeleteFile", array(array('key' => 'action' , 'value' => 'modify'),
																																																				 array('key' => 'id' , 'value' => $this->http->getParam("id")),
																																																				 array('key' => 'db' , 'value' => $currentModel->getDatabase()),
																																																				 array('key' => 'table' , 'value' => $currentModel->getTable()),
																																																				 array('key' => 'column' , 'value' => $column),
																																																				 array('key' => 'type' , 'value' => $result["attributes"][0]["value"])));
					}
				}
				
				// Search type uniqid
				$result = $this->xmlType->getTags("//sls_configs/entry[@table='".$this->db."_".$currentModel->getTable()."' and @column='".$column."' and @type='uniqid']");
				if (!empty($result))
				{					
					$values = array();
					$form = "input_text";
					$align = "left";
					$multilanguage = $defaultMultilanguage;
					$fk = -1;
					$date = "false";
					$color = "false";
					$defaultValue = $columns[$i]->Default;
					$values = substr(md5(time().substr(sha1(microtime()),0,rand(12,25))),mt_rand(1,20),40);
					$urlAC = "";
					$jsType = "string";
					$jsSpecificType = "uniqid";
				}
				
				// Search type ip
				$result = array_shift($this->xmlType->getTags("//sls_configs/entry[@table='".$this->db."_".$currentModel->getTable()."' and @column='".$column."' and (@type='ip_both' or @type='ip_v4' or @type='ip_v6')]/@type"));
				if (!empty($result))
				{					
					$values = array();
					$form = "input_text";
					$align = "left";
					$multilanguage = $defaultMultilanguage;
					$fk = -1;
					$date = "false";
					$color = "false";
					$defaultValue = $columns[$i]->Default;
					$values = $_SERVER["REMOTE_ADDR"];
					$urlAC = "";
					$jsType = "string";
					$jsSpecificType = $result;
				}
				
				// Search type color
				$result = $this->xmlType->getTags("//sls_configs/entry[@table='".$this->db."_".$currentModel->getTable()."' and @column='".$column."' and @type='color']");
				if (!empty($result))
				{					
					$values = array();
					$form = "input_text";
					$align = "right";
					$multilanguage = $defaultMultilanguage;
					$fk = -1;
					$date = "false";
					$color = "true";
					$defaultValue = $columns[$i]->Default;
					$urlAC = "";
					$jsType = "string";
					$jsSpecificType = "color";
				}
				
				// Search filters
				$jsFilter = array();
				$results = $this->xmlFilter->getTags("//sls_configs/entry[@table='".$this->db."_".$currentModel->getTable()."' and @column='".$column."']/@filter");
				if (!empty($results))				
					foreach($results as $result)
						array_push($jsFilter,$result);
				
				// Search filter password
				$this->_generic->useModel(SLS_String::tableToClass($this->model),$this->db);
				$class = ucfirst($this->db)."_".SLS_String::tableToClass($this->model);
				$currentModel = new $class();
				$result = $this->xmlFilter->getTags("//sls_configs/entry[@table='".$this->db."_".$currentModel->getTable()."' and @column='".$column."' and @filter='hash']");
				if (!empty($result))
				{
					$values = array();
					$form = "input_password";
					$align = "left";
					$multilanguage = $defaultMultilanguage;
					$fk = -1;
					$typeFile = -1;
					$thumbs = array();
					$date = "false";
					$color = "false";
					$urlAC = "";
					$jsType = "string";
					$jsSpecificType = "";
					$nullable = "true";
				}
				
				// Search FK
				$res = $this->xmlFk->getTagsByAttributes("//sls_configs/entry",array("tableFk","columnFk"),array($this->db."_".$currentModel->getTable(),$column));
				if (!empty($res))
				{
					$resultFk = array_shift($this->xmlFk->getTagsAttribute("//sls_configs/entry[@tableFk='".$this->db."_".$currentModel->getTable()."' and @columnFk='".$column."' and @multilanguage = 'false']","multilanguage"));
					$labelPk = substr($res,(strpos($res,'labelPk="')+9),(strpos($res,'" tablePk="')-(strpos($res,'labelPk="')+9)));					
					$tableTm = substr($res,(strpos($res,'tablePk="')+9),(strpos($res,'"/>')-(strpos($res,'tablePk="')+9)));							
					$tablePk = SLS_String::substrAfterFirstDelimiter($tableTm,"_");
					$dbPk 	 = SLS_String::substrBeforeFirstDelimiter($tableTm,"_");			
					
					$form = "input_ac";
					$align = "right";
					$multilanguage = (!empty($resultFk)) ? "false" : $defaultMultilanguage;
					$length = -1;
					$fk = $tablePk;
					$typeFile = -1;
					$thumbs = array();
					$date = "false";
					$color = "false";
					$defaultValue = $columns[$i]->Default;
					$jsType = "string";
					$jsSpecificType = "fk";
					$urlAddFk = $this->_generic->getFullPath($controllerBo = array_shift($this->_generic->getControllersXML()->getTags("//controllers/controller[@isBo='true']/@name")),"Add".ucfirst($dbPk)."_".SLS_String::tableToClass($tablePk),
																		  array(array("key" => "SlsQuick", "value" => "iFrame")),false);
										
					$currentModel->getModel($this->http->getParam("id"));					
					$this->_generic->useModel($tablePk,$dbPk,"user");
					$class = ucfirst($dbPk)."_".SLS_String::tableToClass($tablePk);
					$object = new $class();					
					$pk = $object->getPrimaryKey();
					$acPattern = $labelPk;
									
					if ($object->getModel($currentModel->__get($column)))
					{
						$params = $object->getParams();						
						foreach($params as $key => $value)						
							if (SLS_String::contains($labelPk,$key))							
								$labelPk = str_replace($key,$value,$labelPk);
					}
					
					$str = $labelPk;
					
					if ($object->getModel($currentModel->__get($column)))
					{
						$params = $object->getParams();
						foreach($params as $key => $value)
							if (SLS_String::contains($acPattern,$key))
								$acPattern = str_replace($key,$object->getColumnComment($key),$acPattern);						
					}					
					
					foreach($object->getParams() as $key => $value)					
						if (SLS_String::contains($str,$key))
							$str = str_replace($key,$object->getColumnComment($key),$str);
					
					$values = $str;
					$urlAC = $this->_generic->getFullPath($controllerBo = array_shift($this->_generic->getControllersXML()->getTags("//controllers/controller[@isBo='true']/@name")),"FkAC",
																		  array(array("key" => "Model",	"value" => $this->model),
																				array("key" => "Db",	"value" => $this->db),
																				array("key" => "Column","value" => $column),
																				array("key" => "Lang",	"value" => "")),false);
					
					/*
					$values = array();
					$arrayTmp = $object->searchModels();
					if ($columns[$i]->Null == "YES")
					{
						$tmp = array("id"	=>"",
									 "label"=>"",
									 "lang" =>"");
						array_push($values,$tmp);
					}
					for($j=0 ; $j<$count=count($arrayTmp) ; $j++)
					{
						$lang = (isset($arrayTmp[$j]->pk_lang)) ? $arrayTmp[$j]->pk_lang : "";
						
						$replacement = array();
						foreach($masks as $cur_mask)						
								array_push($replacement,trim($arrayTmp[$j]->{$cur_mask}));						
						
						$tmp = array("id"	=>$arrayTmp[$j]->$pk,
									 "label"=>str_replace($masks,$replacement,$str),
									 "lang" =>$lang);
						array_push($values,$tmp);
					}*/
				}
				
				// Search no multilanguage
				$result = array_shift($this->xmlBo->getTagsAttribute("//sls_configs/entry[@table='".$this->db."_".$currentModel->getTable()."' and @column='".$column."' and @multilanguage = 'false']","multilanguage"));
				$multilanguage = (!empty($result)) ? "false" : "true";
				
				$comment = ($columns[$i]->Comment == "") ? $column : $columns[$i]->Comment;				
				$currentColumn = array("form_column"		=> $column,
								   	   "form_type" 			=> $form,
								   	   "form_align" 		=> $align,
								   	   "form_multilanguage" => $multilanguage,
								   	   "form_type_file"		=> $typeFile,
								   	   "form_thumbs"		=> $thumbs,
								   	   "form_length"		=> $length,
								   	   "form_label" 		=> $comment,
									   "form_date"			=> $date,
									   "form_color"			=> $color,
								   	   "form_values"		=> $values,
								   	   "foreign_key"		=> $fk,
								   	   "form_null"			=> $nullable,
									   "form_ac_pattern"	=> $acPattern,
									   "form_url_ac"		=> $urlAC,
				 					   "form_url_add_fk"	=> $urlAddFk,
									   "form_url_delete"	=> $urlDelete,
									   "js_type"			=> $jsType,
									   "js_specific_type"	=> $jsSpecificType,
									   "js_filters"			=> $jsFilter);
				array_push($properties,$currentColumn);
			}
		}
		return $properties;
	}
}
?>